#!/usr/bin/env python3
# -*- coding: utf8 -*-

# CRAP5 - 5-bit Compact Representation of Alphabetical Patterns
# Copyright © 2023 Nichlas Severinsen
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program.  If not, see <https://www.gnu.org/licenses/>.


import re
import sys
import string
import argparse
import textwrap

import crap5


if __name__ == 'crap5.__main__':

    parser = argparse.ArgumentParser('CRAP5 encoder/decoder')
    parser.add_argument('-d', '--decode', action='store_true', help='Decode data')
    parser.add_argument('-i', '--infile', type=argparse.FileType('rb'), default=(None if sys.stdin.isatty() else sys.stdin.buffer.raw))
    parser.add_argument('-o', '--outfile', type=argparse.FileType('wb'), default=sys.stdout.buffer)
    parser.add_argument('-u', '--uppercase', action='store_true', help='Print decoded data as uppercase')
    parser.add_argument('-x', '--hex', action='store_true', help='Print encoded data as hex')
    parser.add_argument('-b', '--bin', action='store_true', help='Print encoded data as binary')
    args = parser.parse_args()

    if not args.infile:
        print('No input given through either STDIN or input file. Do --help to see options. Nothing left to do. Terminating.')
        sys.exit()

    if args.decode:

        for decoded in crap5.decode(args.infile):
            if args.uppercase:
                sys.stdout.buffer.write(decoded)
            else:
                sys.stdout.buffer.write(decoded.lower())

        sys.stdout.buffer.write(b'\n')

    else:

        try:
            if args.bin:
                bitdict = {x.to_bytes(1, 'big'): '{0:08b}'.format(x).encode('utf8') for x in range(0,crap5.BASE_BINARY**crap5.BYTE_LENGTH)}

            for byte in crap5.encode(args.infile):
                if args.bin:
                    sys.stdout.buffer.write(bitdict[byte] + b' ')
                elif args.hex:
                    sys.stdout.buffer.write(byte.hex().encode('utf8'))
                else:
                    sys.stdout.buffer.write(byte)

            sys.stdout.buffer.write(b'\n')
        except KeyError as err:
            sys.stdout.buffer.write(b'\n')
            sys.stdout.flush()
            sys.stderr.buffer.write(b"ERROR: Unknown character %s. Please sanitize your input. Terminating.\n" % str(err).encode('utf8'))
            sys.exit(1)


sys.exit()

